/******************************************************************************

  Copyright (C), 2020-2025, HiFace Tech. Co., Ltd.

  HiFace Camera Interface  (HCI)
  HiFace Camera Module  (HCM)

以下四个函数接口必须存在，以主应用先关联
  HCM_USRPLATFORM_Init
  HCM_USRPLATFORM_UnInit
  HCM_USRPLATFORM_DealAiNalyseData
  HCM_USRPLATFORM_GetInfo

1. 海飞主进程 调用
2. libusrplatform.so（HCM_USRPLATFORM_Init）
3. 创建两个线程
4. 线程1运行start_usrsoft.sh ------> 启动用户软件uavdetr
5. 线程2运行OSD_test ------> 接收来自uavdetr的消息并更新OSD

******************************************************************************/

#include <errno.h>
#include <netinet/in.h>
#include <pthread.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/prctl.h>
#include <sys/socket.h>
#include <sys/time.h>
#include <unistd.h>

#include "hci_def.h"
#include "hci_intf.h"
#include "hci_struct.h"
#include "hcmComInfo.h"

#define OK 0UL
#define ERR 1UL

#define PORT 18500
#define BUFFER_SIZE 20

CHAR *pVersion = "m400 v1.0.0";
HCI_FUNC *gpHciFunc = NULL;

void *OSD_test();
void *start_usersoft_thread();

// 主进程起来会去调用 HCM_USRPLATFORM_Init
// 注意此函数不能阻塞, 用户可以开启线程方式来初始化
// 可以通过pstHcFunc 来获取设备相关信息接口
INT HCM_USRPLATFORM_Init(HCI_FUNC *pstHcFunc)
{
    gpHciFunc = pstHcFunc;

    pthread_t osd_thread_id;       // 线程ID
    pthread_t usersoft_thread_id;  // 线程ID
    printf("主线程开始执行。\n");

    // 创建线程
    if (pthread_create(&osd_thread_id, NULL, OSD_test, NULL) != 0)
    {
        perror("无法创建线程");
        return 1;
    }

    if (pthread_create(&usersoft_thread_id, NULL, start_usersoft_thread, NULL) != 0)
    {
        perror("无法创建线程");
        return 1;
    }

    // 分离线程
    pthread_detach(osd_thread_id);
    pthread_detach(usersoft_thread_id);
    printf("主线程结束执行。\n");

    return 0;
}

INT HCM_USRPLATFORM_UnInit(VOID)
{
    printf("HCM_USRPLATFORM_UnInit...\n");
    gpHciFunc = NULL;
    return 0;
}

CHAR *HCM_USRPLATFORM_GetInfo(VOID) { return pVersion; }

void *start_usersoft_thread()
{
<<<<<<< HEAD
	return pVersion;
}

void* start_usersoft_thread(){
  // sleep(30);
  system("/date/start_usrsoft.sh &");
  return 0;
=======
    sleep(30);
    system("/date/start_usrsoft.sh &");
    return 0;
>>>>>>> 2dd58938c36388ac0bace2238403bf78dac18975
}

void *OSD_test()
{
<<<<<<< HEAD
  // sleep(20);
  int sockfd;  
  uint8_t buffer[BUFFER_SIZE];  
  struct sockaddr_in servaddr, cliaddr;  
  HCM_VI_SENSOR_S vi_cfg;
  HCM_OSD_S osd_cfg;
  
  char* wp[5]={"关","跟踪 ","强光 ","声效 ","天线 "};
  char* target_name[4]={"无 ","人 ","无人机 ","载具 "};

  gpHciFunc->Intf_GetParam(HCI_CFG_OSD,0,&osd_cfg,sizeof(osd_cfg));

  osd_cfg.stTitleOSD[0].wPosX=14;
  osd_cfg.stTitleOSD[0].wPosY=404;

  osd_cfg.stTitleOSD[1].wPosX=276;
  osd_cfg.stTitleOSD[1].wPosY=5;

  osd_cfg.stTitleOSD[2].wPosX=14;
  osd_cfg.stTitleOSD[2].wPosY=480;

  strcpy(osd_cfg.stTitleOSD[0].szText,"反制措施  关\n倍率 2");
  strcpy(osd_cfg.stTitleOSD[1].szText,"水平 N/A | 垂直 N/A");
  strcpy(osd_cfg.stTitleOSD[2].szText,"反制目标 无人机");

  gpHciFunc->Intf_SetParam(HCI_CFG_OSD,0,&osd_cfg,sizeof(osd_cfg));

  // 创建套接字  
  if ((sockfd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {  
      perror("socket creation failed");  
      exit(EXIT_FAILURE);  
  }  

  memset(&servaddr, 0, sizeof(servaddr));  
  memset(&cliaddr, 0, sizeof(cliaddr));  

  // 填充服务器信息  
  servaddr.sin_family = AF_INET; // IPv4  
  servaddr.sin_addr.s_addr = INADDR_ANY;  
  servaddr.sin_port = htons(PORT);  

  // 绑定套接字到端口  
  if (bind(sockfd, (const struct sockaddr *)&servaddr, sizeof(servaddr)) < 0) {  
      perror("bind failed");  
      close(sockfd);  
      exit(EXIT_FAILURE);  
  }  

  int n;  
  socklen_t len = sizeof(cliaddr);  

  while (1) {  
      // 接收客户端消息  
      n = recvfrom(sockfd, (char *)buffer, BUFFER_SIZE, MSG_WAITALL, (struct sockaddr *)&cliaddr, &len);  
      if(n>=8){
        gpHciFunc->Intf_GetParam(HCI_CFG_OSD,0,&osd_cfg,sizeof(osd_cfg));
        char write_buf[64];  
        char wExpTimeMax[7];
        char recv_num[7];

        switch (buffer[2])
=======
    sleep(20);
    int sockfd;
    uint8_t buffer[BUFFER_SIZE];
    struct sockaddr_in servaddr, cliaddr;
    HCM_VI_SENSOR_S vi_cfg;
    HCM_OSD_S osd_cfg;

    char *wp[5] = {"关", "跟踪 ", "强光 ", "声效 ", "天线 "};
    char *target_name[4] = {"无 ", "人 ", "无人机 ", "载具 "};

    gpHciFunc->Intf_GetParam(HCI_CFG_OSD, 0, &osd_cfg, sizeof(osd_cfg));

    osd_cfg.stTitleOSD[0].wPosX = 14;
    osd_cfg.stTitleOSD[0].wPosY = 404;

    osd_cfg.stTitleOSD[1].wPosX = 276;
    osd_cfg.stTitleOSD[1].wPosY = 5;

    osd_cfg.stTitleOSD[2].wPosX = 14;
    osd_cfg.stTitleOSD[2].wPosY = 480;

    strcpy(osd_cfg.stTitleOSD[0].szText, "反制措施  关\n倍率 2");
    strcpy(osd_cfg.stTitleOSD[1].szText, "水平 N/A | 垂直 N/A");
    strcpy(osd_cfg.stTitleOSD[2].szText, "反制目标 无人机");

    gpHciFunc->Intf_SetParam(HCI_CFG_OSD, 0, &osd_cfg, sizeof(osd_cfg));

    // 创建套接字
    if ((sockfd = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
    {
        perror("socket creation failed");
        exit(EXIT_FAILURE);
    }

    memset(&servaddr, 0, sizeof(servaddr));
    memset(&cliaddr, 0, sizeof(cliaddr));

    // 填充服务器信息
    servaddr.sin_family = AF_INET;  // IPv4
    servaddr.sin_addr.s_addr = INADDR_ANY;
    servaddr.sin_port = htons(PORT);

    // 绑定套接字到端口
    if (bind(sockfd, (const struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
    {
        perror("bind failed");
        close(sockfd);
        exit(EXIT_FAILURE);
    }

    int n;
    socklen_t len = sizeof(cliaddr);

    while (1)
    {
        // 接收客户端消息
        n = recvfrom(sockfd, (char *)buffer, BUFFER_SIZE, MSG_WAITALL, (struct sockaddr *)&cliaddr,
                     &len);
        if (n >= 8)
>>>>>>> 2dd58938c36388ac0bace2238403bf78dac18975
        {
            gpHciFunc->Intf_GetParam(HCI_CFG_OSD, 0, &osd_cfg, sizeof(osd_cfg));
            char write_buf[64];
            char wExpTimeMax[7];
            char recv_num[7];

            switch (buffer[2])
            {
                // 更新曝光
                case 1:
                    sprintf(write_buf, "反制措施 ");
                    // char uwp[25];

                    if (!buffer[3]) strcat(write_buf, wp[0]);
                    if (buffer[3] & 0x01) strcat(write_buf, wp[1]);
                    if (buffer[3] & 0x02) strcat(write_buf, wp[2]);
                    if (buffer[3] & 0x04) strcat(write_buf, wp[3]);
                    if (buffer[3] & 0x08) strcat(write_buf, wp[4]);

                    char zoom[3];
                    zoom[1] = '\0';
                    zoom[2] = '\0';

                    if (buffer[4] > 9)
                    {
                        uint8_t unitPlace = buffer[4] / 1 % 10;  // 个位
                        uint8_t tenPlace = buffer[4] / 10 % 10;  // 十位
                        zoom[0] = tenPlace + '0';
                        zoom[1] = unitPlace + '0';
                    }
                    else
                    {
                        zoom[0] = buffer[4] + '0';
                    }

                    strcat(write_buf, "\n倍率 ");
                    strcat(write_buf, zoom);

                    strcpy(osd_cfg.stTitleOSD[buffer[2] - 1].szText, write_buf);
                    gpHciFunc->Intf_SetParam(HCI_CFG_OSD, 0, &osd_cfg, sizeof(osd_cfg));
                    break;
                case 2:
                    sprintf(write_buf, "水平 ");
                    uint16_t num_int = buffer[3] << 4 | buffer[4] >> 4;
                    uint16_t num_fra = buffer[4] & 0x0F;
                    sprintf(recv_num, "%d.", num_int);
                    strcat(write_buf, recv_num);
                    sprintf(recv_num, "%d", num_fra);
                    strcat(write_buf, recv_num);

                    strcat(write_buf, " | 垂直 ");
                    if (buffer[6] >> 4) strcat(write_buf, "-");
                    num_fra = buffer[6] & 0x0F;
                    sprintf(recv_num, "%d.", buffer[5]);
                    strcat(write_buf, recv_num);
                    sprintf(recv_num, "%d", num_fra);
                    strcat(write_buf, recv_num);

                    strcpy(osd_cfg.stTitleOSD[buffer[2] - 1].szText, write_buf);
                    gpHciFunc->Intf_SetParam(HCI_CFG_OSD, 0, &osd_cfg, sizeof(osd_cfg));
                    break;
                case 3:
                    sprintf(write_buf, "反制目标 ");

                    if (buffer[3] & 0x01) strcat(write_buf, target_name[0]);
                    if (buffer[3] & 0x02) strcat(write_buf, target_name[1]);
                    if (buffer[3] & 0x04) strcat(write_buf, target_name[2]);
                    if (buffer[3] & 0x08) strcat(write_buf, target_name[3]);

                    strcpy(osd_cfg.stTitleOSD[buffer[2] - 1].szText, write_buf);
                    gpHciFunc->Intf_SetParam(HCI_CFG_OSD, 0, &osd_cfg, sizeof(osd_cfg));
                case 4:
                    gpHciFunc->Intf_GetParam(HCI_CFG_ISP_SENSOR, 3, &vi_cfg, sizeof(vi_cfg));

                    if (!vi_cfg.byAutoExposureEx)
                    {
                        sprintf(wExpTimeMax, "%d", vi_cfg.wExpTimeMax);
                    }
                    else
                    {
                        sprintf(wExpTimeMax, "%d", vi_cfg.wExpoSuretime);
                    }
                    sendto(sockfd, (const void *)wExpTimeMax, strlen(write_buf), MSG_CONFIRM,
                           (const struct sockaddr *)&cliaddr, len);
                    break;
            }
        }
        usleep(100);
    }

    return 0;
}